﻿/*
* Activity Tracking Log v0.1.1 - http://activitytrackinglog.codeplex.com
* Activity Tracking Log for ASP.Net & ASP.Net MVC
* Copyright (c) 2011 Vadim Burac
* Licensed under the Microsoft Public License (Ms-PL)
* http://activitytrackinglog.codeplex.com/license
*/

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web;
using ActivityTrackingLog.Configuration;
using System.Web.Security;
using ActivityTrackingLog.Storage;
using ActivityTrackingLog.Data;
using ActivityTrackingLog.Utils;
using ActivityTrackingLog.Data.DTOs;

namespace ActivityTrackingLog.Utils
{
    public static class Log
    {
        private static ILogRepository logRepository = null;

        static Log()
        {
            logRepository = Factory.LogRepository;
        }

        public static ActivityItemDTO LogActivity(Enum category, Enum activity, bool isPostAction = false)
        {
            var activityCode = Convert.ChangeType(activity, activity.GetTypeCode());
            return LogActivity(category.ToString(), activity.ToString(), isPostAction, activityCode.ToString());
        }

        public static ActivityItemDTO LogActivity(string category, string activity, bool isPostAction = false, string activityCode = null)
        {
            return LogActivity(ActivityTypeEnum.UserServerSide, activity, true, category, isPostAction, activityCode);
        }

        internal static ActivityItemDTO LogActivity(ActivityTypeEnum type, 
            string activity, 
            bool recordPageUrl, 
            string category = null, 
            bool isPostAction = false,
            string activityCode = null,
            string pageUrl = null,
            string queryString = null)
        {
            if (!Enabled)
                return null;

            var context = HttpContext.Current;

            string localPageUrl = pageUrl;
            string localQueryString = queryString;
            string userKey = null;
            string clientHost = null;
            string userAgent = null;
            if (null != context)
            {
                if (recordPageUrl)
                {
                    string[] urlParts = context.Request.RawUrl.Split(new[] { '?' });
                    localPageUrl = urlParts[0];
                    if (urlParts.Length > 1)
                        localQueryString = urlParts[1];
                }

                // get current user id
                if (context.Request.IsAuthenticated)
                {
                    /*MembershipUser currentUser = Membership.GetUser(false);
                    if (null != currentUser)
                        userId = currentUser.ProviderUserKey.ToString();*/
                    userKey = context.User.Identity.Name;
                }

                clientHost = context.Request.UserHostAddress;
                if (Config.Log.LogUserAgent)
                    userAgent = context.Request.UserAgent;
            }

            return LogActivity(userKey: userKey, 
                clientHost: clientHost,
                appKey: Config.Log.ApplicationKey,
                type: type, 
                category: category, 
                activity: activity, 
                isPostAction: isPostAction,
                activityCode: activityCode,
                pageUrl: localPageUrl,
                queryString: localQueryString,
                userAgent: userAgent);
        }

        private static ActivityItemDTO LogActivity(
            string userKey, 
            string clientHost, 
            string appKey, 
            ActivityTypeEnum type, 
            string category, 
            string activity, 
            bool isPostAction = false,
            string activityCode = null, 
            string pageUrl = null, 
            string queryString = null,
            string userAgent = null)
        {
            if (!Enabled)
                return null;

            // create activity item
            ActivityItem userActivity = new ActivityItem(userKey: userKey,
                clientHost: clientHost,
                applicationKey: appKey,
                activityType: type,
                category: category,
                activity: activity,
                isPostAction: isPostAction,
                activityCode: activityCode,
                pageUrl: pageUrl,
                queryString: queryString);
            // validate and create user agent item
            if (!string.IsNullOrWhiteSpace(userAgent))
            {
                UserAgentItem userAgentItem = new UserAgentItem();
                var hashValue = userAgent.ToSha256Base64();
                userAgentItem.ApplicationKey = Config.Log.ApplicationKey;
                userAgentItem.UserAgentId = Guid.NewGuid();
                userAgentItem.Hash = hashValue;
                userAgentItem.AgentString = userAgent;
                // save agent data
                userActivity.UserAgentItem = userAgentItem;
            }

            logRepository.Save(userActivity);

            return userActivity.GetDTO();
        }

        #region helpers

        private static bool Enabled
        {
            get
            {
                return Config.Log.Enabled && Config.Storage.Enabled;
            }
        }

        #endregion
    }
}
